package com.spa.infrastructure.mybatisplus;

import cn.hutool.core.collection.CollectionUtil;
import com.baomidou.mybatisplus.annotation.TableName;
import com.spa.infrastructure.annotation.UrlParse;
import com.spa.infrastructure.service.storage.FileService;
import com.spa.infrastructure.service.storage.StorageType;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.ObjectUtils;
import org.apache.ibatis.executor.resultset.ResultSetHandler;
import org.apache.ibatis.plugin.*;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.core.annotation.AnnotationUtils;
import org.springframework.stereotype.Component;

import java.lang.reflect.Field;
import java.sql.Statement;
import java.util.ArrayList;
import java.util.Objects;
import java.util.StringJoiner;

@Slf4j
@Component
@Intercepts({
        @Signature(type = ResultSetHandler.class, method = "handleResultSets", args = {Statement.class})
})
public class ResultSetInterceptor implements Interceptor {

    @Autowired
    private FileService fileService;

    @Override
    public Object intercept(Invocation invocation) throws Throwable {
        //取出查询的结果
        Object resultObject = invocation.proceed();
        if (Objects.isNull(resultObject)) {
            return null;
        }
        //基于selectList
        if (resultObject instanceof ArrayList) {
            @SuppressWarnings("unchecked")
            ArrayList<Objects> resultList = (ArrayList<Objects>) resultObject;
            if (!CollectionUtil.isEmpty(resultList) && needToWrapper(resultList.get(0))) {
                for (Object result : resultList) {
                    wrapper(result);
                }
            }
            //基于selectOne
        } else {
            if (needToWrapper(resultObject)) {
                wrapper(resultObject);
            }
        }
        return resultObject;
    }

    private boolean needToWrapper(Object object) {
        Class<?> objectClass = object.getClass();
        TableName tableName = AnnotationUtils.findAnnotation(objectClass, TableName.class);
        return Objects.nonNull(tableName);
    }

    public <T> T wrapper(T result) throws IllegalAccessException {
        //取出resultType的类
        Class<?> resultClass = result.getClass();
        Field[] declaredFields = resultClass.getDeclaredFields();
        for (Field field : declaredFields) {
            //取出所有被UrlParse注解的字段
            UrlParse urlParse = field.getAnnotation(UrlParse.class);
            if (!Objects.isNull(urlParse)) {
                field.setAccessible(true);
                Object object = field.get(result);
                if(ObjectUtils.isEmpty(object)){
                    continue;
                };
                //String的解密
                if (object instanceof String value) {
                    if (urlParse.hasMore()) {
                        String split = urlParse.split();
                        StringJoiner stringJoiner = new StringJoiner(split);
                        for (String s : value.split(split)) {
                            stringJoiner.add(fileService.getUrl(s, StorageType.QINIUYUN));
                        }
                        field.set(result, stringJoiner.toString());
                    } else {
                        field.set(result, fileService.getUrl(value, StorageType.QINIUYUN));
                    }
                }
            }
        }
        return result;
    }

}
